# coding: utf-8

import json
from datetime import datetime

from sqlalchemy import text

from common.bid_notify.constant import ActionType, IMContentType
from common.bid_notify.utils import JPush
from common.utils import DB, redis_client
from common.im_util import im_client
from common.schedule.demand_utils import clear_cache
from common.bid_notify.app_message import AppMessage, AppContent
from common.bid_notify.wx_content import WXContent
from common.constant import (
    USE_SMS_BID_WIN_NOTIFY, WECHAT_QUEUE, APP_USER_ID_KEY,
    COMMON_API_QUEUE, TAIWAN_CODE)
from common.im_util import SYS_IM_NOTIFY_FROM, CS_ACCID2, IMMessageType
from common.producer import Producer
from common.bid_notify.sql_statement import Statement
from common.models import (
    model_factory, DemandStatus, get_timestamp,
    DemandCate)


class NotifyBase(object):

    @classmethod
    def batch_send_wx_message(cls, data_list):
        """
        created by chenhj at 2018/4/12
        """
        wechat_producer = Producer(WECHAT_QUEUE)
        queue_send_count = 100
        for i in range(0, len(data_list), queue_send_count):
            wechat_producer.send(
                json.dumps(data_list[i:i + queue_send_count]))

    @classmethod
    def batch_send_app_message(
            cls, session, im_from, to_ids, message, msg_type, push_title=''):
        """
        通过im发送通知消息
        发送消息内容必须一致
        """
        if not isinstance(to_ids, list) and not to_ids:
            return
        insert_values = list()
        for to_id in to_ids:
            to_id = str(to_id)
            group_id = '%s:%s:%s' % tuple(
                sorted([str(im_from), to_id, str(msg_type)[0]])
            )
            msg_item = dict(message)
            insert_values.append(
                (
                    im_from,
                    to_id,
                    msg_type,
                    json.dumps(msg_item, ensure_ascii=False),
                    group_id
                )
            )
        insert_values = list(map(
            lambda x:
            '(\'%s\', \'%s\', %s, %r, \'%s\', '
            'false, UNIX_TIMESTAMP() * 1000, UNIX_TIMESTAMP())' % x,
            insert_values
        ))
        if insert_values:
            value_text = ', '.join(insert_values)
            session.execute(
                text(Statement.insert_im_msg_sql.format(
                    insert_values=value_text))
            )
        im_client.batch_sys_msg(
            im_from,
            to_ids,
            dict(
                data=message,
                msg_type=msg_type
            ),
            push_title
        )


class MessageNotify(NotifyBase):

    @classmethod
    def send_winner_msg(cls, demand, user, partic, mobile, session=None):
        """
        create by ld_wu 2017-11-27
        发送中标通知，包括微信、app及短信的方式
        :return:
        """
        cls._bid_notify(
            session, demand, user, partic, mobile
        )

        clear_cache(demand.id)

    @classmethod
    def recharge_notify(cls, demand, user, pack, partic, session=None):
        """
        create_by ld_wu 2018-01-27
        竞拍成功但余额不足，发送提醒充值通知
        """
        template_data = WXContent.recharge_content(
            session,
            demand,
            user,
            pack
        )
        cls.send_wx_message(user, template_data)
        content = AppContent.recharge_content(demand, pack, partic)
        title = '余额不足'
        message_type = IMMessageType.CLIENT.value
        msg = content['msg']
        AppMessage.send_msg(
            session,
            CS_ACCID2,
            user.id,
            content,
            message_type,
            title,
            ios_msg=dict(
                apsField=dict(
                    alert=dict(
                        body=msg,
                        title=title
                    ),
                    message_type=message_type,
                    action_type=ActionType.ACCOUNT,
                )
            ),
            android_msg=msg,
            android_ext=dict(
                action_type=ActionType.ACCOUNT,
            )
        )

    @classmethod
    def follow_notify(cls, demand, user, mobile, partic, session=None):
        template_data = WXContent.follow_content(
            session,
            demand,
            user
        )
        cls.send_wx_message(user, template_data)
        content = AppContent.follow_content(demand, mobile, partic)
        title = '确认跟进状态'
        message_type = IMMessageType.CHAT.value
        msg = content['msg']
        AppMessage.send_msg(
            session,
            demand.uid,
            user.id,
            content,
            message_type,
            title,
            ios_msg=dict(
                apsField=dict(
                    alert=dict(
                        body=msg,
                        title=title
                    ),
                    message_type=message_type,
                    demand_id=demand.id,
                    demand_status=partic.demand_status,
                    action_type=ActionType.DEMAND_DETAIL,
                )
            ),
            android_msg=msg,
            android_ext=dict(
                demand_id=demand.id,
                demand_status=partic.demand_status,
                action_type=ActionType.DEMAND_DETAIL,
            )
        )

    @classmethod
    def approval_notify(
        cls, demand, user, partic, add_point=0, minus_credit=0, session=None
    ):
        """
        created by chenhj at 2018/4/2

        """
        template_data = WXContent.approval_content(
            session,
            demand,
            user,
            partic,
            add_point
        )
        cls.send_wx_message(user, template_data)
        content = AppContent.approval_content(demand, partic, add_point, minus_credit)
        title = '反馈结果'
        message_type = IMMessageType.CLIENT.value
        msg = content['msg']
        AppMessage.send_msg(
            session,
            CS_ACCID2,
            user.id,
            content,
            message_type,
            title,
            ios_msg=dict(
                apsField=dict(
                    alert=dict(
                        body=msg,
                        title=title
                    ),
                    message_type=message_type,
                    demand_id=demand.id,
                    demand_status=partic.demand_status,
                    action_type=ActionType.DEMAND_DETAIL,
                )
            ),
            android_msg=msg,
            android_ext=dict(
                demand_id=demand.id,
                demand_status=partic.demand_status,
                action_type=ActionType.DEMAND_DETAIL,
            )
        )

    @classmethod
    def timeout_payback_notify(cls, session, demand, user, ret_bid_point):
        """
        created by chenhj at 2018/6/12

        """
        template_data = WXContent.timeout_payback_content(
            session, demand, user, ret_bid_point
        )
        cls.send_wx_message(user, template_data, session)
        content = AppContent.timeout_payback_content(demand, ret_bid_point)
        title = '退款通知'
        message_type = IMMessageType.CLIENT.value
        msg = content['msg']
        AppMessage.send_msg(
            session,
            CS_ACCID2,
            user.id,
            content,
            message_type,
            title,
            ios_msg=dict(
                apsField=dict(
                    alert=dict(
                        body=msg,
                        title=title
                    ),
                    message_type=message_type,
                    demand_id=demand.id,
                    demand_status=demand.status,
                    action_type=ActionType.DEMAND_DETAIL,
                )
            ),
            android_msg=msg,
            android_ext=dict(
                demand_id=demand.id,
                demand_status=demand.status,
                action_type=ActionType.DEMAND_DETAIL,
            )
        )

    @classmethod
    def expired_red_packet_notify(cls, red_packet_id, bid_point):
        with DB() as session:
            red_packet = model_factory.bid_point_red_packet.get_by_id(
                session,
                red_packet_id
            )
            title = '红包退还通知'
            msg = '退还汇币'
            if red_packet.receiver_id:
                target_type = '好友'
                user = model_factory.user.get_by_id(session, red_packet.receiver_id)
                target_name = user.nickname if user else ''
            else:
                target_type = '群聊'
                group_info = im_client.group_info(red_packet.im_group_id)
                target_name = group_info.get('tname', '')
            app_msg = dict(
                msg=msg,
                title=title,
                type=IMContentType.EXPIRED_RED_PACKET,
                ext=json.dumps(
                    dict(
                        reason='发送至{}"{}"的汇币红包，超过24小时未被领取'.format(
                            target_type, target_name
                        ),
                        way='退还汇币',
                        arrived_time=datetime.now().strftime('%F %H:%M'),
                        bid_point=bid_point,
                        red_packet_id=red_packet_id,
                        for_sys=True,  # 客服系统消息
                        action_type=ActionType.RED_PACKET_DETAIL,
                        btn_name='查看详情↓↓↓'
                    )
                )
            )
            AppMessage.send_msg(
                session,
                CS_ACCID2,
                red_packet.sender_id,
                app_msg,
                IMMessageType.CLIENT.value,
                title
            )

    @classmethod
    def bid_winner_call_notify(cls, session, partic, demand, mobile):
        """
        created by chenhj at 2018/6/12
        提醒工程商及时联系客户
        """
        user = model_factory.user.get_by_id(session, partic.supplier_id)
        template_data = WXContent.bid_winner_notify_content(
            session, partic, user
        )
        cls.send_wx_message(user, template_data, session)
        im_from = demand.uid
        im_to = partic.supplier_id
        # 消息类型（竞标成功提醒）
        message_type = IMMessageType.CHAT.value
        app_msg = AppContent.winner_notify_content(demand, mobile)
        title = '订单即将超时'
        msg = app_msg['msg']
        AppMessage.send_msg(
            session, im_from, im_to, app_msg, message_type, title,
            ios_msg=dict(
                apsField=dict(
                    alert=dict(
                        body=msg,
                        title=title
                    ),
                    message_type=message_type,
                    demand_id=demand.id,
                    demand_status=partic.demand_status,
                    action_type=ActionType.DEMAND_DETAIL,
                )
            ),
            android_msg=msg,
            android_ext=dict(
                demand_id=demand.id,
                demand_status=partic.demand_status,
                action_type=ActionType.DEMAND_DETAIL,
            )
        )

        clear_cache(demand.id)

    @classmethod
    def _bid_notify(cls, session, demand, user, partic, mobile):
        template_data = WXContent.winner_content(
            session,
            demand,
            user,
            partic
        )
        cls.send_wx_message(user, template_data)

        im_from = demand.uid
        im_to = partic.supplier_id
        # 消息类型（竞标成功提醒）
        message_type = IMMessageType.CHAT.value
        app_msg = AppContent.winner_content(demand, mobile)
        msg = app_msg['msg']
        title = '竞拍成功'
        AppMessage.send_msg(
            session, im_from, im_to, app_msg, message_type, title,
            ios_msg=dict(
                apsField=dict(
                    alert=dict(
                        body=msg,
                        title=title
                    ),
                    message_type=message_type,
                    demand_id=demand.id,
                    demand_status=partic.demand_status,
                    action_type=ActionType.DEMAND_DETAIL,
                )
            ),
            android_msg=msg,
            android_ext=dict(
                demand_id=demand.id,
                demand_status=partic.demand_status,
                action_type=ActionType.DEMAND_DETAIL,
            )
        )

    @classmethod
    def add_wx_send_log(cls, user, template_data, session, code='', url=''):
        """
        created by chenhj at 2018/4/13

        """
        model_factory.wechat_send_log.create(
            session,
            user_id=user.id,
            user_nickname=user.nickname,
            user_mobile=user.mobile,
            openid=user.wx_openid,
            url=template_data.get('url', url),
            code=code,
            content=json.dumps(template_data, ensure_ascii=False)
        )

    @classmethod
    def send_wx_message(cls, user, template_data, session=None):
        use_sms_send_flag = json.loads(
            redis_client.get(USE_SMS_BID_WIN_NOTIFY) or 'false'
        )

        if not use_sms_send_flag:
            # 发送中标模板消息
            if user.wx_openid:
                with DB(session) as session:
                    cls.add_wx_send_log(user, template_data, session)
                    send_data = [template_data]
                    cls.batch_send_wx_message(send_data)

    @classmethod
    def send_training_notify(cls, session, demand, user):
        if user.wx_openid:
            (
                template_id,
                data,
                url,
                cate_name,
                demand_info_text
            ) = WXContent.new_order_content(
                session, demand, for_training=True
            )

            send_data = [{
                'openid': user.wx_openid,
                'template_id': template_id,
                'data': data,
                'url': url
            }]
            cls.batch_send_wx_message(send_data)
        app_msg = AppContent.new_order_content(demand)
        cls.batch_send_app_message(
            session, SYS_IM_NOTIFY_FROM, [user.id], app_msg, IMMessageType.TRAINING_ORDER.value
        )

    def new_notify(
        self, demand_id,
        demand_status=0, direct_notify=False, admin_user_id=0
    ):
        """
        create_by ld_wu 2017-11-28
        新项目通知
        """
        from common.bid_notify.notify_handler import MasterDispatchHandler

        with DB() as session:

            message_type = IMMessageType.NEW_ORDER.value

            demand = model_factory.demand.get_by_id(session, demand_id)
            if demand.published_count == 1 and demand.notify_limit <= 0:
                demand.status = DemandStatus.COMPETE_DONE.value
                return
            old_status = demand.status

            if demand.cate == DemandCate.MAINTAIN.value:
                demand.status = max(int(DemandStatus.SECOND_ONGOING.value), demand_status)
            else:
                # 避免发布状态为发布中，如果状态有问题，走主人派单流程
                current_status = (
                    demand.status
                    if demand.status != DemandStatus.PUBLISHING.value
                    else
                    DemandStatus.MASTER_DISPATCHING.value
                )
                # 修改项目状态
                demand.status = demand_status or current_status

                # 如果项目状态为主人派单,但该项目没有enterprise_id,则改为普通派单
                if demand.status == DemandStatus.MASTER_DISPATCHING.value and not demand.enterprise_id:
                    demand.status = DemandStatus.DISPATCHING.value

            demand_owner = model_factory.user.get_by_id(session, demand.uid)
            notify_users = MasterDispatchHandler(
                session,
                demand
            ).publish_handler(
                direct_notify=direct_notify,
                demand_owner=demand_owner
            )
            if notify_users and demand.area_id != TAIWAN_CODE:
                # 写入订单分配统计
                common_producer = Producer(COMMON_API_QUEUE)
                common_producer.send(
                    json.dumps(
                        dict(
                            backend='demand_stat',
                            func='day_stat',
                            kwargs=dict(
                                demand_status=demand.status,
                                published_count=demand.published_count,
                                demand_id=demand.id
                            )
                        )
                    )
                )
            # 主人派单和派单暂时样式保持一致
            if demand.status in (DemandStatus.DISPATCHING.value, DemandStatus.MASTER_DISPATCHING.value):
                # 消息类型（派单提醒）
                message_type = IMMessageType.DISPATCH_ORDER.value
            if demand.status == DemandStatus.BRONZE_MEDAL_DISCOUNT.value:
                # 消息类型(优先抢单)
                message_type = IMMessageType.BRONZE_DISCOUNT_ORDER.value

            # 发布日志
            self.publish_log(session, demand, admin_user_id, old_status)

            # 更新发布时间
            demand.published_at = get_timestamp()
            im_from = SYS_IM_NOTIFY_FROM

            # 每300条发送一次
            queue_send_count = 300
            app_user_id_set = {
                int(each) for each in redis_client.smembers(APP_USER_ID_KEY)
            }
            template_id, data, url, _, demand_info = WXContent.new_order_content(
                session, demand,
            )

            message = self.im_new_msg_content(demand, demand_info)
            # 安装订单、维修订单。。
            title = '{}订单'.format(demand.cate_display)

            send_app_user_ids = list()

            for i in range(0, len(notify_users), queue_send_count):
                send_users = notify_users[i: i + queue_send_count]
                send_ids = [x.id for x in send_users]
                send_app_user_ids.extend(list(app_user_id_set & set(send_ids)))

                # 发送微信通知
                wx_send_data = []
                for each in send_users:
                    if each.wx_openid:
                        wx_send_data.append({
                            'openid': each.wx_openid,
                            'template_id': template_id,
                            'data': data,
                            'url': url
                        })
                        self.add_wx_send_log(
                            each, data, session, 'NEW_ORDER', url)
                self.batch_send_wx_message(wx_send_data)

            # im或者极光推送与微信分开，避免频繁调用接口
            for i in range(0, len(send_app_user_ids), queue_send_count):
                app_user_ids = send_app_user_ids[i: i + queue_send_count]

                # 发送im通知(IOS)
                im_client.batch_sys_msg(
                    im_from,
                    app_user_ids,
                    dict(
                        apsField=dict(
                            alert=dict(
                                body=self.push_new_msg_content(demand),
                                title=title
                            ),
                            message_type=message_type,
                            demand_id=demand.id,
                            demand_status=demand.status,
                            action_type=ActionType.DEMAND_DETAIL,
                        )
                    ),
                    title
                )

                insert_values = list()
                for user_id in app_user_ids:
                    group_id = '%s:%s:%s' % tuple(
                        sorted(
                            [str(im_from), str(user_id), str(message_type)[0]])
                    )
                    msg_item = dict(message)
                    insert_values.append(
                        (
                            im_from,
                            user_id,
                            message_type,
                            json.dumps(msg_item, ensure_ascii=False),
                            group_id
                        )
                    )

                insert_values = list(map(
                    lambda x:
                    '(\'%s\', \'%s\', %s, %r, \'%s\', '
                    'false, UNIX_TIMESTAMP() * 1000, UNIX_TIMESTAMP())' % x,
                    insert_values
                ))
                if insert_values:
                    value_text = ', '.join(insert_values)
                    session.execute(
                        text(Statement.insert_im_msg_sql.format(
                            insert_values=value_text))
                    )

            # 极光推送
            JPush().smart_send_by_alias(
                self.push_new_msg_content(demand),
                send_app_user_ids,
                title,
                ext=dict(
                    demand_id=demand_id,
                    demand_status=demand.status,
                    action_type=ActionType.DEMAND_DETAIL,
                ),
                notify_tile='你有1条LED屏订单',
                notify_content='快速点击查看客户联系方式，以免错过最佳营销时机！'
            )
        clear_cache(demand_id)

    @classmethod
    def publish_log(cls, session, demand, admin_user_id, old_status):
        # 管理员操作的才会有发布日志
        if admin_user_id:
            # 发布日志和统计
            model_factory.publish_demand_log.create(
                session,
                admin_id=admin_user_id,
                demand_id=demand.id,
                old_demand_status=old_status,
                new_demand_status=demand.status,
                published_count=demand.published_count,
                published_at=demand.published_at,
                notice_way=1,             # 通知微信
                notice_pay=False,
                dispatch_count=demand.dispatch_count
            )

    @classmethod
    def im_new_msg_content(cls, demand, demand_info):
        """
        create by ld_wu 2018-05-18
        IM 新订单消息内容
        :return:
        """
        return dict(
            type=0,
            ext=json.dumps(dict(
                demand_id=demand.id,
                demand_status=demand.status
            )),
            msg='{cate}订单，位置：{city} {demand_info}'.format(
                cate=demand.cate_display,
                city=demand.city,
                demand_info=demand_info
            )
        )

    @classmethod
    def push_new_msg_content(cls, demand):
        """
        create by ld_wu 2018-05-18
        推送的新订单内容
        :param demand:
        :return:
        """
        dispatch_status = (
            DemandStatus.DISPATCHING.value,
            DemandStatus.MASTER_DISPATCHING.value
        )
        if demand.status in dispatch_status:
            tag = '【派单尊享】'
        elif demand.status == DemandStatus.BRONZE_MEDAL_DISCOUNT.value:
            tag = '【优先抢单】'
        else:
            tag = ''

        return '{}{}'.format(tag, demand.new_msg_content)

    def new_arrival_msg(self, im_from, to_id, message, title):
        with DB() as session:
            insert_values = list()
            # 客服消息
            msg_type = IMMessageType.CLIENT.value
            group_id = '%s:%s:%s' % tuple(
                sorted([str(im_from), str(to_id), str(msg_type)[0]])
            )
            send_msg = dict(
                msg=message,
                title=title,
                type=IMContentType.FIRST_LOGIN,
                ext=json.dumps(
                    dict(
                        for_sys=True,
                        action_type=ActionType.DEMAND_LIST,
                        btn_name='速戳立即抢单↓↓↓'
                    )
                )
            )
            insert_values.append(
                (
                    im_from,
                    to_id,
                    msg_type,
                    json.dumps(send_msg, ensure_ascii=False),
                    group_id
                )
            )
            insert_values = list(map(
                lambda x:
                '(\'%s\', \'%s\', %s, %r, \'%s\', '
                'false, UNIX_TIMESTAMP() * 1000, UNIX_TIMESTAMP())' % x,
                insert_values
            ))
            if insert_values:
                value_text = ', '.join(insert_values)
                session.execute(
                    text(Statement.insert_im_msg_sql.format(insert_values=value_text))
                )

    @classmethod
    def app_invite_new_user_notify(cls, session, invite_user, user, invite_datetime):
        """
        created by chenhj at 2018/6/28
        邀请到新下线后, 通知我(在该下线登录时), 只进行im通知
        @:param invite_user: 邀请人
        @:param user: 下线
        @:param invite_datetime: 邀请时间
        """
        content = AppContent.app_invite_new_user_content(
            invite_user, user, invite_datetime
        )
        title = '新增成员通知'
        message_type = IMMessageType.CLIENT.value
        msg = content['msg']
        AppMessage.send_msg(
            session,
            CS_ACCID2,
            invite_user.id,
            content,
            message_type,
            title,
            ios_msg=dict(
                apsField=dict(
                    alert=dict(
                        body=msg,
                        title=title
                    ),
                    message_type=message_type,
                    action_type=ActionType.RELATION_PAGE,
                )
            ),
            android_msg=msg,
            android_ext=dict(
                action_type=ActionType.RELATION_PAGE,
            )
        )

    @classmethod
    def app_voucher_ending_notify(cls, session, users):
        """
        created by chenhj at 2018/7/6
        代金券即将到期 app通知
        """
        title = '代金券即将到期'
        content = (
            '您有价值{}元代金券今日到期，尽快抢单使用哦！'
        )
        message_type = IMMessageType.CLIENT.value
        app_msg = dict(
            msg=None,
            title=title,
            type=IMContentType.RECHARGE,
            ext=json.dumps(
                dict(
                    for_sys=True,  # 客服系统消息
                    action_type=ActionType.ACCOUNT,
                    btn_name='查看我的代金券↓↓↓'
                )
            )
        )
        for each in users:
            msg = content.format(each.bid_point)
            app_msg['msg'] = msg
            AppMessage.send_msg(
                session,
                CS_ACCID2,
                each.id,
                app_msg,
                message_type,
                title,
                ios_msg=dict(
                    apsField=dict(
                        alert=dict(
                            body=msg,
                            title=title
                        ),
                        message_type=message_type,
                        action_type=ActionType.ACCOUNT,
                    )
                ),
                android_msg=msg,
                android_ext=dict(
                    action_type=ActionType.ACCOUNT,
                )
            )

    @classmethod
    def app_give_voucher_notify(cls, user_id, count):
        """
        created by lina at 2018/7/10
        赠送代金券 app通知
        """
        with DB() as session:
            title = '代金券已到账'
            content = (
                '已赠送您{}张价值200元无门槛代金券，快去我的账户查收吧！'
            )
            message_type = IMMessageType.CLIENT.value
            app_msg = dict(
                msg=None,
                title=title,
                type=IMContentType.RECHARGE,
                ext=json.dumps(
                    dict(
                        user_id=user_id,
                        for_sys=True,  # 客服系统消息
                        action_type=ActionType.ACCOUNT,
                        btn_name='查看我的代金券↓↓↓'
                    )
                )
            )
            msg = content.format(count)
            app_msg['msg'] = msg
            AppMessage.send_msg(
                session,
                CS_ACCID2,
                user_id,
                app_msg,
                message_type,
                title,
                ios_msg=dict(
                    apsField=dict(
                        alert=dict(
                            body=msg,
                            title=title
                        ),
                        message_type=message_type,
                        action_type=ActionType.ACCOUNT,
                    )
                ),
                android_msg=msg,
                android_ext=dict(
                    action_type=ActionType.ACCOUNT,
                )
            )

    @classmethod
    def lock_return_dispatch_notify(cls, user_id, demand_id, session=None):
        """
        created by chenhj at 2018/8/2

        """
        with DB(session) as session:
            demand = model_factory.demand.get_by_id(session, demand_id)
            user = model_factory.user.get_by_id(session, user_id)
            template_data = WXContent.lock_return_dispatch_content(
                session, demand, user
            )
            cls.send_wx_message(user, template_data, session)

            message_type = IMContentType.DISPATCH_RETURN
            app_msg = AppContent.lock_return_dispatch_content(
                demand, message_type
            )
            AppMessage.send_msg(
                session,
                CS_ACCID2,
                user_id,
                app_msg,
                IMMessageType.CLIENT.value,
                app_msg['title'],
                ios_msg=dict(
                    apsField=dict(
                        alert=dict(
                            body=app_msg['msg'],
                            title=app_msg['title']
                        ),
                        message_type=message_type,
                        demand_id=demand.id,
                        demand_status=DemandStatus.DISPATCHING.value,
                        action_type=ActionType.DEMAND_DETAIL,
                    )
                ),
                android_msg=app_msg['msg'],
                android_ext=dict(
                    message_type=message_type,
                    demand_id=demand.id,
                    demand_status=DemandStatus.DISPATCHING.value,
                    action_type=ActionType.DEMAND_DETAIL,
                )
            )
